package com.dcy.common.base.interceptor;

import cn.hutool.core.annotation.AnnotationUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ClassLoaderUtil;
import cn.hutool.core.util.ReflectUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.toolkit.StringPool;
import com.baomidou.mybatisplus.extension.plugins.handler.DataPermissionHandler;
import com.dcy.common.annotation.DataScopeColumn;
import com.dcy.common.constant.SqlConstant;
import com.dcy.common.model.LoginAccount;
import com.dcy.common.utils.AdminLoginUtil;
import lombok.extern.slf4j.Slf4j;
import net.sf.jsqlparser.expression.Expression;
import net.sf.jsqlparser.expression.StringValue;
import net.sf.jsqlparser.expression.operators.conditional.AndExpression;
import net.sf.jsqlparser.expression.operators.relational.ExpressionList;
import net.sf.jsqlparser.expression.operators.relational.InExpression;
import net.sf.jsqlparser.expression.operators.relational.ItemsList;
import net.sf.jsqlparser.schema.Column;

import java.util.Set;
import java.util.stream.Collectors;

/**
 * @author dcy
 * @description 数据权限实现
 * @createTime 2023/1/2 9:38
 */
@Slf4j
public class DcyDataPermissionHandler implements DataPermissionHandler {

    @Override
    public Expression getSqlSegment(Expression where, String mappedStatementId) {
        //获取mapper名称
        String className = StrUtil.subBefore(mappedStatementId, StringPool.DOT, true);
        //获取方法名
        String methodName = StrUtil.subAfter(mappedStatementId, StringPool.DOT, true);
        //获取注解  来判断是不是要拼接sql
        DataScopeColumn dataScopeColumn = AnnotationUtil.getAnnotation(ReflectUtil.getMethodByName(ClassLoaderUtil.loadClass(className), methodName), DataScopeColumn.class);
        if (dataScopeColumn != null) {
            return dataPermissionHandler(dataScopeColumn, where);
        }
        return where;
    }


    /**
     * 数据权限处理
     * 使用方式：mapper方法上 加上 @InterceptorIgnore 注解
     *
     * @param dataScopeColumn 权限注解
     * @param where           条件
     */
    private Expression dataPermissionHandler(DataScopeColumn dataScopeColumn, Expression where) {
        if (StrUtil.equals(dataScopeColumn.name(), SqlConstant.DEFAULT_DATA_SCOPE_COLUMN)) {
            final LoginAccount userInfo = AdminLoginUtil.getUserInfo();
            // 不是拥有所有数据权限
            if (userInfo != null && !userInfo.getAllDataScopeFlag()) {
                // 有数据范围
                Set<String> dataScopeList = userInfo.getDataScopes();
                if (where != null && CollUtil.isNotEmpty(dataScopeList)) {
                    ItemsList itemsList = new ExpressionList(dataScopeList.stream().map(StringValue::new).collect(Collectors.toList()));
                    String column = getAliasColumn(dataScopeColumn);
                    return new AndExpression(where, new InExpression(new Column(column), itemsList));
                }
            }
        }
        return where;
    }


    /**
     * 获取字段名称
     *
     * @param dataScopeColumn
     * @return
     */
    private String getAliasColumn(DataScopeColumn dataScopeColumn) {
        String column = dataScopeColumn.name();
        if (StrUtil.isNotBlank(dataScopeColumn.alias())) {
            column = StrUtil.builder().append(dataScopeColumn.alias()).append(StringPool.DOT).append(dataScopeColumn.name()).toString();
        }
        return column;
    }
}
